package com.atguigu.auth.controller;

/**
 * ClassName: IndexController
 * Package: com.atguigu.auth.controller
 * Description:
 *
 * @Author 蹇泽阳
 * @Create 2023/11/13 20:48
 * @Version 1.0
 */

import com.atguigu.auth.mapper.SysUserMapper;
import com.atguigu.auth.service.SysMenuService;
import com.atguigu.auth.utils.MenuHelper;
import com.atguigu.common.Result;
import com.atguigu.common.execption.GuiguException;
import com.atguigu.common.jwt.JwtHelper;
import com.atguigu.common.util.MD5;
import com.atguigu.model.system.SysMenu;
import com.atguigu.model.system.SysUser;
import com.atguigu.vo.system.LoginVo;
import com.atguigu.vo.system.MetaVo;
import com.atguigu.vo.system.RouterVo;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * <p>
 * 后台登录登出
 * </p>
 */
@Api(tags = "后台登录管理")
@RestController
@RequestMapping("/admin/system/index")
public class IndexController {
  @Autowired
  private SysUserMapper sysUserMapper;
  @Autowired
  private SysMenuService sysMenuService;
  
  @ApiOperation(value = "登录")
  @PostMapping("login")
  public Result login(@RequestBody LoginVo loginVo) {
    // 1. 获取输入用户名和密码
    String username = loginVo.getUsername();
    // 2. 根据用户名查询数据库
    LambdaQueryWrapper<SysUser> lambdaQueryWrapper = new LambdaQueryWrapper<>();
    lambdaQueryWrapper.eq(SysUser::getUsername, username);
    SysUser sysUser = sysUserMapper.selectOne(lambdaQueryWrapper);
    // 3. 用户信息是否存在
    if (null == sysUser) {
      throw new GuiguException(201, "用户不存在");
    }
    // 4. 判断密码
    if (!MD5.encrypt(loginVo.getPassword()).equals(MD5.encrypt(loginVo.getPassword()))) {
      throw new GuiguException(201, "密码错误");
    }
    // 5. 判断用户是否被禁用
    if (sysUser.getStatus().intValue() == 0) {
      throw new GuiguException(201, "用户被禁用");
    }
    // 6. 使用jwt根据用户id和用户名生成token
    Map<String, Object> map = new HashMap<>();
    // 7. 返回token
    map.put("token", JwtHelper.createToken(sysUser.getId(), sysUser.getUsername()));
    return Result.ok(map);
  }
  
  // /**
  //  * 登录
  //  * @return
  //  */
  // @PostMapping("login")
  // @ApiOperation("登录")
  // public Result login() {
  //   Map<String, Object> map = new HashMap<>();
  //   map.put("token","admin");
  //   return Result.ok(map);
  // }
  
  /**
   * 获取用户信息
   *
   * @return
   */
  @GetMapping("info")
  @ApiOperation("获取用户信息")
  public Result info(HttpServletRequest request) {
    // 1. 从请求头获取token
    String header = request.getHeader("token");
    // 2. 根据token获取用户id
    Long userId = JwtHelper.getUserId(header);
    // 3. 根据用户id查询用户信息
    SysUser sysUser = sysUserMapper.selectById(userId);
    // 4. 根据用户id获取用户可以操作的菜单权限数据
    List<SysMenu> routerVoList = sysMenuService.findUserMenuList(userId); // 当前用户的菜单权限数据
    List<SysMenu> menus = MenuHelper.buildTree(routerVoList); // 转换为树状结构
    List<RouterVo> voList = buildMenus(menus);// 构建路由
    // 5. 根据用户id获取用户可以操作的按钮权限数据
    List<String> permsList = sysMenuService.findUserPermsByUserId(userId);
    
    Map<String, Object> map = new HashMap<>();
    map.put("roles", "[admin]");
    map.put("name", sysUser.getUsername());
    map.put("avatar", "https://oss.aliyuncs.com/aliyun_id_photo_bucket/default_handsome.jpg");
    // 返回用户可以操作的菜单权限数据
    map.put("routers", voList);
    // 返回用户可以操作的按钮权限数据
    map.put("buttons", permsList);
    
    return Result.ok(map);
  }
  
  /**
   * 退出
   *
   * @return
   */
  @PostMapping("logout")
  @ApiOperation("退出")
  public Result logout() {
    return Result.ok();
  }
  
  
  /**
   * 根据菜单构建路由
   *
   * @param menus
   * @return
   */
  private List<RouterVo> buildMenus(List<SysMenu> menus) {
    List<RouterVo> routers = new LinkedList<RouterVo>();
    for (SysMenu menu : menus) {
      RouterVo router = new RouterVo();
      router.setHidden(false);
      router.setAlwaysShow(false);
      router.setPath(getRouterPath(menu));
      router.setComponent(menu.getComponent());
      router.setMeta(new MetaVo(menu.getName(), menu.getIcon()));
      List<SysMenu> children = menu.getChildren();
      // 如果当前是菜单，需将按钮对应的路由加载出来，如：“角色授权”按钮对应的路由在“系统管理”下面
      if (menu.getType().intValue() == 1) {
        List<SysMenu> hiddenMenuList = children.stream().filter(item -> !StringUtils.isEmpty(item.getComponent())).collect(Collectors.toList());
        for (SysMenu hiddenMenu : hiddenMenuList) {
          RouterVo hiddenRouter = new RouterVo();
          hiddenRouter.setHidden(true);
          hiddenRouter.setAlwaysShow(false);
          hiddenRouter.setPath(getRouterPath(hiddenMenu));
          hiddenRouter.setComponent(hiddenMenu.getComponent());
          hiddenRouter.setMeta(new MetaVo(hiddenMenu.getName(), hiddenMenu.getIcon()));
          routers.add(hiddenRouter);
        }
      } else {
        if (!CollectionUtils.isEmpty(children)) {
          if (children.size() > 0) {
            router.setAlwaysShow(true);
          }
          router.setChildren(buildMenus(children));
        }
      }
      routers.add(router);
    }
    return routers;
  }
  
  /**
   * 获取路由地址
   *
   * @param menu 菜单信息
   * @return 路由地址
   */
  public String getRouterPath(SysMenu menu) {
    String routerPath = "/" + menu.getPath();
    if (menu.getParentId().intValue() != 0) {
      routerPath = menu.getPath();
    }
    
    return routerPath;
  }
  
}
